﻿using FasterWPF;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Shapes;

namespace WPFContrib
{
    public class SquaresNavigator 
    {    
        private Canvas _cvs = null;
        private StackPanel _stkPanl = null;
        private FontSettings before = null;
        private FontSettings after = null;
        private Border _nameDisplayBorder = null;
        private Border _titleBorder = null;

        public Label NameDisplayLabel
        {
            get { return _nameDisplayBorder.GetChildFromComposite<Label, StackPanel>(0, 0); }
        }

        public Label TitleLabel
        {
            get { return _titleBorder.GetChildFromComposite<Label, Canvas>(0, 0); }
        }

        public StackPanel InnerStackPanel
        {
            get { return _stkPanl; }
            set { _stkPanl = value; }
        }

        public Canvas InnerCanvas
        {
            get { return _cvs; }
            set { _cvs = value; }
        }
        
        public SquaresNavigator()
        {
            _stkPanl = new StackPanel();
            _stkPanl.Background = Brushes.Transparent;
            _stkPanl.Initialize(610.0D, 190.0D, ContainerType.ContentControlPanel, Orientation.Vertical);
            _stkPanl.BeginSettings()
                .Set<Label, StackPanel>("Height", 35.0D)
                .Set<Label, StackPanel>("Width", 595.0D)
                .SetItemBorderSettings(Double.NaN, Double.NaN, Brushes.Black, new Thickness(1, 1, 1, 1))
                .EndSettings();

            _cvs = new Canvas();
            _cvs.Height = 150.0D;
            _cvs.Width = 610.0D;
            _cvs.Initialize(ContainerType.ContentControlPanel);
            _cvs.BeginSettings().Set<Label, Canvas>(0, 0, "Height", 20.0D).Set<Label, Canvas>(0, 0, "Padding", new Thickness(1)).EndSettings();

            before = FontExt.CreateFont("Segoe UI", 9.0, FontWeights.Normal, FontStyles.Normal);  //not currently used, placeholder in case numbering desired in squares
            after = FontExt.CreateFont("Segoe UI", 9.0, FontWeights.Bold, FontStyles.Normal);  //not currently used, placeholder in case numbering desired in squares
        }

        public void AddSquares(long totalRecords, List<string> cachedDisplayNamesForSubsetOfIDs, string columnName, string tableName, Brush backgroundBrush, Brush colorOfSquares, Action<object, System.Windows.Input.MouseButtonEventArgs, string, string, string> loadDataAction, Action<object, ValueChangedEventArgs, string, string, string> onMouseOverAction)
        {
            List<long> counterList = new List<long>();

            long increment = totalRecords / 400;

            long counter = 0;
            for (double degree=0.0D; degree < 401.0D; degree++)
            {              
               counter += increment;
               long storeCounter = counter;
               counterList.Add(storeCounter);
            }

            string storeCounter2 = counterList[0].ToString();
            
           _titleBorder = _cvs.BeginComposite().AddLabel(0,0,"Squares Navigation", Brushes.Gray).EndComposite(new CanvasArgs(0, 0, 1));

            _cvs.BeginComposite()
               .AddFlatButton(0, 0, 59.0, 20.0, "Start", Brushes.Black, new Thickness(1.0), backgroundBrush, new CornerRadius(1.0), new Thickness(1.0, 1.0, 1.0, 1.0), new Thickness(0.0), colorOfSquares, Brushes.Black, Brushes.Black, before, after, (o, me) => { long counterCopy = 0; loadDataAction(o, me, counterCopy.ToString(), 198.ToString(), "Start"); })
               .SubscribeDependencyEventOnChild<Border, Canvas>(0, 0, "IsMouseDirectlyOverChanged", ((o, me) => { long counterCopy2 = 0; onMouseOverAction(o, me, counterCopy2.ToString(), 198.ToString(), "Start"); }))
               .EndComposite(new CanvasArgs(0, 20, 1));

            AddFlatButtons(_cvs, 1.0D, 51.0D, 41.0D, increment, 2, counterList, cachedDisplayNamesForSubsetOfIDs, backgroundBrush, colorOfSquares, loadDataAction, onMouseOverAction);

            AddFlatButtons(_cvs, 51.0D, 101.0D, 52.0D, increment, 3, counterList, cachedDisplayNamesForSubsetOfIDs, Brushes.AntiqueWhite, colorOfSquares, loadDataAction, onMouseOverAction);

            AddFlatButtons(_cvs, 101.0D, 151.0D, 63.0D, increment, 4, counterList, cachedDisplayNamesForSubsetOfIDs, backgroundBrush, colorOfSquares, loadDataAction, onMouseOverAction);

            AddFlatButtons(_cvs, 151.0D, 201.0D, 74.0D, increment, 5, counterList, cachedDisplayNamesForSubsetOfIDs, Brushes.AntiqueWhite, colorOfSquares, loadDataAction, onMouseOverAction);

            AddFlatButtons(_cvs, 201.0D, 251.0D, 85.0D, increment, 6, counterList, cachedDisplayNamesForSubsetOfIDs, backgroundBrush, colorOfSquares, loadDataAction, onMouseOverAction);

            AddFlatButtons(_cvs, 251.0D, 301.0D, 96.0D, increment, 7, counterList, cachedDisplayNamesForSubsetOfIDs, Brushes.AntiqueWhite, colorOfSquares, loadDataAction, onMouseOverAction);

            AddFlatButtons(_cvs, 301.0D, 351.0D, 107.0D, increment, 8, counterList, cachedDisplayNamesForSubsetOfIDs, backgroundBrush, colorOfSquares, loadDataAction, onMouseOverAction);

            AddFlatButtons(_cvs, 351.0D, 401.0D, 118.0D, increment, 9, counterList, cachedDisplayNamesForSubsetOfIDs, Brushes.AntiqueWhite, colorOfSquares, loadDataAction, onMouseOverAction);

            _cvs.BeginComposite()
             .AddFlatButton(0, 0, 59.0, 20.0, "End", Brushes.Black, new Thickness(1.0), backgroundBrush, new CornerRadius(1.0), new Thickness(1.0, 1.0, 1.0, 1.0), new Thickness(0.0), colorOfSquares, Brushes.Black, Brushes.Black, before, after, (o, me) => { long counterCopy = counterList[400] + increment; loadDataAction(o, me, counterCopy.ToString(), 1000.ToString(), "End"); })
             .SubscribeDependencyEventOnChild<Border, Canvas>(0, 0, "IsMouseDirectlyOverChanged", (o, me) => { long counterCopy2 = counterList[400] + increment; onMouseOverAction(o, me, counterCopy2.ToString(), 1000.ToString(), "End"); })
             .EndComposite(new CanvasArgs(0, 130.0, 10));

            _cvs.Background = Brushes.Transparent;
            this.EndInit();
        }

        public void AddFlatButtons(Canvas _cvs, double start, double end, double? top, long increment, int zIndex, List<long> counterList, List<string> cachedFundNames, Brush backgroundBrush, Brush colorOfSquares, Action<object, System.Windows.Input.MouseButtonEventArgs, string, string, string> loadDataAction, Action<object, ValueChangedEventArgs, string, string, string> onMouseOverAction)
        {
            for (double degree = start; degree < end; degree++)
            {
                double offset = degree - start;
                long storeLong = counterList[(int)degree];
                string storeName = cachedFundNames[(int)degree];
                _cvs.BeginComposite()
                     .AddFlatButton(0, 0, 12.0, 12.0, degree.ToString(), Brushes.Black, new Thickness(1.0), backgroundBrush, new CornerRadius(1.0), new Thickness(1.0, 1.0, 1.0, 1.0), new Thickness(0.0), colorOfSquares, Brushes.Transparent, Brushes.Transparent, before, after, (o, me) => { long counterCopy = storeLong; string storeAgain = storeName; loadDataAction(o, me, counterCopy.ToString(), increment.ToString(), storeAgain); })
                     .SubscribeDependencyEventOnChild<Border, Canvas>(0, 0, "IsMouseDirectlyOverChanged", ((o, me) => { long counterCopy2 = storeLong; string storeAgain = storeName; onMouseOverAction(o, me, counterCopy2.ToString(), increment.ToString(), storeAgain); }))
                     .EndComposite(new CanvasArgs(offset * 12.0D, top, zIndex));
            }
        }

        public static StringBuilder GetProportionalListOfIDs(long totalRecords)
        {
            long counter = 0;            
            long increment = totalRecords / 400;

            StringBuilder sb = new StringBuilder();

            for (double degree = 0.0D; degree < 401.0D; degree++)
            {
                counter += increment;
                long storeCounter = counter;

                sb.Append("'0',");
                if (degree != 400)
                {
                    sb.Append("'" + storeCounter.ToString() + "',");
                }
                else
                {
                    sb.Append("'" + storeCounter.ToString() + "'");
                }
            }

            return sb;
        }

        public void EndInit()
        {
            _stkPanl.BeginComposite()
                      .AddExisting<Canvas, StackPanel>(0, 0, _cvs)
                      .EndComposite<StackPanel, StackPanelArgs>(new StackPanelArgs(Orientation.Vertical));

            _nameDisplayBorder = _stkPanl.BeginComposite()
                .AddLabel(0, 0, "ID: 0 Start", Brushes.White)
                .EndComposite<StackPanel, StackPanelArgs>(new StackPanelArgs(Orientation.Vertical));
        }
    }
}
